﻿using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using CRM.Anyleads;
using CRM.Models.Email;
using Microsoft.EntityFrameworkCore;

namespace CRM.Services
{
    public class AnyleadsService : BaseService
    {
        private readonly AnyleadsClient _anyleadsClient;
        private readonly MyDbContext _dbContext;
        private readonly EmailDogClient _emailDogClient;

        public AnyleadsService(AnyleadsClient anyleadsClient, MyDbContext dbContext, EmailDogClient emailDogClient)
        {
            _anyleadsClient = anyleadsClient;
            _dbContext = dbContext;
            _emailDogClient = emailDogClient;
        }

        /// <summary>
        /// 验证邮箱有效性并缓存
        /// </summary>
        /// <param name="email"></param>
        /// <returns></returns>
        public async Task<bool> ValidateEmail(string email)
        {
            var emailVerify = await _dbContext.EmailVerifies.Where(e => e.EmailAddress == email).FirstOrDefaultAsync();
            if (null == emailVerify)
            {
                emailVerify = await GetModel(email);
                _dbContext.Add(emailVerify);
            }

            await _dbContext.SaveChangesAsync();
            return emailVerify.State;
        }

        private async Task<EmailVerify> GetModel(string email)
        {
            // var res = await _anyleadsClient.VerifyEmailState(email);
            var res = await _emailDogClient.VerifyEmailState(email);
            return new EmailVerify()
            {
                OemId = CurrentUser.OemId,
                CompanyId = CurrentUser.CompanyId,
                UserId = CurrentUser.Id,
                GroupId = CurrentUser.GroupId,
                EmailAddress = email,
                State = res
            };
        }

        /// <summary>
        /// 批量验证邮箱有效性并缓存
        /// </summary>
        /// <param name="emailList"></param>
        /// <returns></returns>
        public async Task<Dictionary<string, bool>> ValidateEmail(IEnumerable<string> emailList)
        {
            var emailVerifies = await _dbContext.EmailVerifies
                .Where(e => emailList.Contains(e.EmailAddress))
                .Select(e => new {e.EmailAddress, e.State})
                .ToListAsync();
            var diffEmailList = emailList.Except(emailVerifies.Select(e => e.EmailAddress)).ToList();

            // key 重复bug
            var resDic = emailVerifies.ToDictionary(x => x.EmailAddress, x => x.State);
            if (diffEmailList.Any())
            {
                foreach (var diff in diffEmailList)
                {
                    var emailVerify = await GetModel(diff);
                    resDic.Add(diff, emailVerify.State);
                    _dbContext.Add(emailVerify);
                }
            }

            await _dbContext.SaveChangesAsync();
            // Task.Factory.StartNew(AddEmailVerifyLog, this);
            await AddEmailVerifyLog(emailList);
            return resDic;
        }

        private async Task AddEmailVerifyLog(IEnumerable<string> emailList)
        {
            var emailVerifyLogs = await _dbContext.EmailVerifyLogs.Where(m =>
                    m.OemId == CurrentUser.OemId && m.CompanyId == CurrentUser.CompanyId && m.GroupId == CurrentUser.GroupId &&
                    m.UserId == CurrentUser.Id)
                .Where(e => emailList.Contains(e.EmailAddress))
                .ToListAsync();
            var diffLogList = emailList.Except(emailVerifyLogs.Select(e => e.EmailAddress)).ToList();
            var diffEmailVerifies = await _dbContext.EmailVerifies.Where(e => diffLogList.Contains(e.EmailAddress))
                .Select(e => new EmailVerifyLog()
                {
                    OemId = CurrentUser.OemId,
                    CompanyId = CurrentUser.CompanyId,
                    UserId = CurrentUser.Id,
                    GroupId = CurrentUser.GroupId,
                    EmailAddress = e.EmailAddress,
                    State = e.State
                }).ToListAsync();
            await _dbContext.AddRangeAsync(diffEmailVerifies);
            await _dbContext.SaveChangesAsync();
        }
    }
}